package ar.com.solidussource.howmuchservices.web.controller;

import java.util.Date;
import java.util.Iterator;

import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;

import org.apache.log4j.Logger;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.ResponseBody;

import ar.com.solidussource.framework.backend.bo.exception.BusinessException;
import ar.com.solidussource.framework.backend.dao.filter.Page;
import ar.com.solidussource.framework.backend.dao.filter.Result;
import ar.com.solidussource.framework.backend.dao.filter.TableOrder;
import ar.com.solidussource.howmuchservices.backend.bo.UserBO;
import ar.com.solidussource.howmuchservices.backend.bo.UserCRUDBO;
import ar.com.solidussource.howmuchservices.common.entities.Person;
import ar.com.solidussource.howmuchservices.common.entities.User;
import ar.com.solidussource.howmuchservices.common.entities.filter.UserFilter;
import ar.com.solidussource.howmuchservices.utils.mail.SendMail;

@Controller
@RequestMapping("/user")
public class UserController extends BaseController {
	private static final Logger log = Logger.getLogger(UserController.class);
	private static final String TABLEORDER_CRITERION = "username";
	private static final String TABLEORDER_DIRECTION = "desc";
	
	private static final String LOGIN_SUCCESS = "success";
	private static final String LOGIN_WRONGPASSWORD = "wrong password";
	private static final String LOGIN_WRONGUSERNAME = "wrong username";
	
	@Autowired UserCRUDBO userCRUDBO;
	@Autowired UserBO userBO;
	
	@RequestMapping(value="/login.json", method = RequestMethod.PUT, produces="application/json")
	@ResponseBody
	public String login(HttpServletResponse httpServletResponse, @RequestParam String username, @RequestParam String password) {
		
		try {
			UserFilter userFilter = new UserFilter();
			userFilter.setUsername(username);
			
			userFilter.setTableOrder(new TableOrder(TABLEORDER_CRITERION, TABLEORDER_DIRECTION));
			Page page = new Page(1, 1);
			
			Result<User> result = userCRUDBO.getAll(userFilter, page);
			
			Iterator<User> ite = result.getResult().iterator();
			
			if (ite.hasNext()) {
				User user = ite.next();
				
				if (user.getUsername().equals(username)) {
					if (user.getPassword().equals(password)) {
						setCurrentUser(user);
						return getJsonStatus(LOGIN_SUCCESS);
					} else {
						return getJsonStatus(LOGIN_WRONGPASSWORD);
					}				
				} else {
					return getJsonStatus(LOGIN_WRONGUSERNAME);
				}
				
			} else {
				return getJsonStatus(LOGIN_WRONGUSERNAME);
			}
			
		} catch (Exception e) {
			httpServletResponse.setStatus(HttpServletResponse.SC_INTERNAL_SERVER_ERROR);
			log.error(e.getMessage(), e);			
			return getJsonStatus(e.getMessage());
		}
 
	}
	
	@RequestMapping(value="/logout.json", method = RequestMethod.PUT, produces="application/json")
	@ResponseBody
	public String logout(HttpServletResponse httpServletResponse, HttpSession session) {
		
		try {			
			session.invalidate();
			
			return getJsonStatus(RESPONSE_OK);
			
		} catch (Exception e) {
			httpServletResponse.setStatus(HttpServletResponse.SC_INTERNAL_SERVER_ERROR);
			log.error(e.getMessage(), e);			
			return getJsonStatus(e.getMessage());
		}
 
	}
	
	@RequestMapping(value="/register.json", method = RequestMethod.PUT, produces="application/json")
	@ResponseBody
	public String register(HttpServletResponse httpServletResponse, @RequestParam String username, @RequestParam String password, @RequestParam String name, @RequestParam String lastname, @RequestParam Date dateofbirth, @RequestParam String email) {
		
		try {
			Person person = new Person();
			person.setName(name);
			person.setLastname(lastname);
			person.setDateofbirth(dateofbirth);
			person.setEmail(email);
			
			person.setCreatedate(new Date());
			
			User user = new User();
			
			user.setPerson(person);
			user.setUsername(username);
			user.setPassword(password);
			
			user.setDeleted(false);
			user.setCreatedate(new Date());
			
			userBO.createUserFromScratch(user);
						
			return getJsonStatus(RESPONSE_OK);
			
		} catch (Exception e) {
			httpServletResponse.setStatus(HttpServletResponse.SC_INTERNAL_SERVER_ERROR);
			log.error(e.getMessage(), e);			
			return getJsonStatus(e.getMessage());
		} 
	}
	
	@RequestMapping(value="/update.json", method = RequestMethod.PUT, produces="application/json")
	@ResponseBody
	public String update(HttpServletResponse httpServletResponse, @RequestParam String username, @RequestParam String password, @RequestParam String name, @RequestParam String lastname, @RequestParam Date dateofbirth, @RequestParam String email) {
		
		try {
			UserFilter userFilter = new UserFilter();
			userFilter.setUsername(username);
			
			userFilter.setTableOrder(new TableOrder(TABLEORDER_CRITERION, TABLEORDER_DIRECTION));
			Page page = new Page(1, 1);
			
			Result<User> result = userCRUDBO.getAll(userFilter, page);
			
			Iterator<User> ite = result.getResult().iterator();
			
			if (ite.hasNext()) {
				User user = ite.next();
				
				user.getPerson().setName(name);
				user.getPerson().setLastname(lastname);
				user.getPerson().setDateofbirth(dateofbirth);
				user.getPerson().setEmail(email);
				
				user.getPerson().setUpdatedate(new Date());
				
				user.setPassword(password);

				user.setUpdatedate(new Date());
				
				userBO.updateUser(user);
							
				return getJsonStatus(RESPONSE_OK);				
				
			} else {
				throw new BusinessException("no user "+username);
			}
						
		} catch (Exception e) {
			httpServletResponse.setStatus(HttpServletResponse.SC_INTERNAL_SERVER_ERROR);
			log.error(e.getMessage(), e);			
			return getJsonStatus(e.getMessage());
		} 
	}	
	
	@RequestMapping(value="/whoami.json", method = RequestMethod.GET, produces="application/json")
	@ResponseBody
	public String whoami(HttpServletResponse httpServletResponse, HttpSession session) {
		
		try {
			User user = getCurrentUser();
			
			if (user == null) {
				return getJsonStatus("no user logged, "+session.getId());
			} else {
				return getJsonStatus(user.getUsername()+", "+session.getId());
			}
						
		} catch (Exception e) {
			httpServletResponse.setStatus(HttpServletResponse.SC_INTERNAL_SERVER_ERROR);
			log.error(e.getMessage(), e);			
			return getJsonStatus(e.getMessage());
		} 
	}
	
	@RequestMapping(value="/passwordrecovery.json", method = RequestMethod.GET, produces="application/json")
	@ResponseBody
	public String passwordRecovery(HttpServletResponse httpServletResponse, @RequestParam String username) {
		
		try {
			
			UserFilter userFilter = new UserFilter();
			userFilter.setUsername(username);
			
			userFilter.setTableOrder(new TableOrder(TABLEORDER_CRITERION, TABLEORDER_DIRECTION));
			Page page = new Page(1, 1);
			
			Result<User> result = userCRUDBO.getAll(userFilter, page);
			
			Iterator<User> ite = result.getResult().iterator();
			
			if (ite.hasNext()) {
				User user = ite.next();
				
				SendMail sendMail = new SendMail("alvgustavoe@gmail.com", "gustavo.alvarez84@gmail.com", "password recovert", "your password is "+user.getPassword());
				
				sendMail.send();
				
				return getJsonStatus(RESPONSE_OK);				
				
			} else {
				throw new BusinessException("no user "+username);
			}
									
		} catch (Exception e) {
			httpServletResponse.setStatus(HttpServletResponse.SC_INTERNAL_SERVER_ERROR);
			log.error(e.getMessage(), e);			
			return getJsonStatus(e.getMessage());
		} 
	}
	
}
